#include <polarisdata/SdramData.h>
#include "stm32f7xx_hal.h"

#define DMA_STREAM DMA2_Stream0
#define DMA_CHANNEL DMA_CHANNEL_0
#define DMA_STREAM_CLOCK() __DMA2_CLK_ENABLE()

DMA_HandleTypeDef DMA_Handle;
uint32_t SdramData::dst = 0xC0800000;

SdramData::SdramData()
{
    DMA_Handle.Instance = DMA_STREAM;
    DMA_Handle.Init.Channel = DMA_CHANNEL;

    rdAddr = 0xC0800000;
}

SdramData::~SdramData()
{
    // TODO 自动生成的析构函数存根
}

int SdramData::isBusy()
{
    if(__HAL_DMA_GET_FLAG(&DMA_Handle,DMA_FLAG_TCIF0_4)==DISABLE)
        return 1;
    else
        return 0;
}

uint32_t SdramData::ReadyToFsmc()
{
//    rt_kprintf("flag :%d\r\n",__HAL_DMA_GET_FLAG(&DMA_Handle,DMA_FLAG_TCIF0_4));返回32->10 0000

    uint32_t num = dst - 0xC0800000 - (rdAddr - 0xC0800000)*2;
    if(num > 1024) return (num - 1024);
    else    if(__HAL_DMA_GET_FLAG(&DMA_Handle,DMA_FLAG_TCIF0_4) == DISABLE) return 0;
            else return num;

}

int SdramData::dma_config(uint32_t src,uint32_t BUFFER_SIZE)
{
//    rt_kprintf("dma_config src:%d,BUFFER_SIZE:%d\r\n",src,BUFFER_SIZE);

//    uint32_t* addr = (uint32_t*)src;
//    rt_kprintf("data 0:%x,data 1:%x\r\n",*addr,*(addr + 1));

    __HAL_DMA_CLEAR_FLAG(&DMA_Handle,DMA_FLAG_TCIF0_4);

    HAL_StatusTypeDef DMA_status = HAL_ERROR;
    DMA_STREAM_CLOCK();
    DMA_Handle.Instance = DMA_STREAM;
    DMA_Handle.Init.Channel = DMA_CHANNEL;
    DMA_Handle.Init.Direction = DMA_MEMORY_TO_MEMORY;
    DMA_Handle.Init.PeriphInc = DMA_PINC_ENABLE;
    DMA_Handle.Init.MemInc = DMA_MINC_ENABLE;
    DMA_Handle.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE;
    DMA_Handle.Init.MemDataAlignment = DMA_PDATAALIGN_BYTE;
    DMA_Handle.Init.Mode = DMA_NORMAL;
    DMA_Handle.Init.Priority = DMA_PRIORITY_HIGH;
    DMA_Handle.Init.FIFOMode = DMA_FIFOMODE_DISABLE;
    DMA_Handle.Init.FIFOThreshold = DMA_FIFO_THRESHOLD_FULL;
    DMA_Handle.Init.MemBurst = DMA_MBURST_SINGLE;
    DMA_Handle.Init.PeriphBurst = DMA_PBURST_SINGLE;

    if(HAL_DMA_Init(&DMA_Handle) != HAL_OK) rt_kprintf("HAL_DMA_Init is not ok!\n");

    DMA_status = HAL_DMA_Start(&DMA_Handle,(uint32_t)src,(uint32_t)dst,BUFFER_SIZE);

    if (DMA_status != HAL_OK) {rt_kprintf("DMA is not ok!\n");return -1;}

    dst = dst + BUFFER_SIZE;
//    rt_kprintf("dst:%x\r\n",dst);
    return 0;
}

void SdramData::rdAddrCount(uint32_t num)
{
    rdAddr+=num;
}
